package net.qktianxia.component.logger.proveder;

import android.support.annotation.NonNull;
import android.support.annotation.Nullable;

import net.qktianxia.component.logger.ILogProxy;
import net.qktianxia.component.logger.IPrinter;
import net.qktianxia.component.logger.orhanobut.logcat.AndroidLogProxy;

/**
 * Created by xiaolong on 2018/8/24.
 * email：xinxiaolong123@foxmail.com
 */

public class Logger {

    IPrinter printer;

    public Logger(Builder builder) {
        setPrinter(builder.printer);
    }

    @NonNull public static Logger.Builder newBuilder() {
        return new Logger.Builder();
    }

    private void setPrinter(@NonNull IPrinter printer) {
        this.printer = printer;
    }

    public void addLogAdapter(@NonNull ILogProxy logProxy) {
        printer.addLogProxy(logProxy);
    }

    public void clearLogProxyList() {
        printer.clearLogProxyList();
    }

    /**
     * Given tag will be used as tag only once for this method call regardless of the tag that's been
     * set during initialization. After this invocation, the general tag that's been set will
     * be used for the subsequent log calls
     */
    public IPrinter t(@Nullable String tag) {
        return printer.t(tag);
    }

    /**
     * General log function that accepts all configurations as parameter
     */
    public void log(int priority, @Nullable String tag, @Nullable String message, @Nullable Throwable throwable) {
        printer.log(priority, tag, message, throwable);
    }


    public void d(@NonNull String message, @Nullable Object... args) {
        printer.d(message, args);
    }

    public void d(@Nullable Object object) {
        printer.d(object);
    }

    public void e(@NonNull String message, @Nullable Object... args) {
        printer.e(null, message, args);
    }

    public void e(@Nullable Throwable throwable, @NonNull String message, @Nullable Object... args) {
        printer.e(throwable, message, args);
    }

    public void i(@NonNull String message, @Nullable Object... args) {
        printer.i(message, args);
    }

    public void v(@NonNull String message, @Nullable Object... args) {
        printer.v(message, args);
    }

    public void w(@NonNull String message, @Nullable Object... args) {
        printer.w(message, args);
    }

    /**
     * Tip: Use this for exceptional situations to log
     * ie: Unexpected errors etc
     */
    public void wtf(@NonNull String message, @Nullable Object... args) {
        printer.wtf(message, args);
    }

    /**
     * Formats the given json content and print it
     */
    public void json(@Nullable String json) {
        printer.json(json);
    }

    /**
     * Formats the given xml content and print it
     */
    public void xml(@Nullable String xml) {
        printer.xml(xml);
    }


    public static class Builder {

        IPrinter printer;

        private Builder() {

        }

        public Builder setPrinter(IPrinter printer) {
            this.printer = printer;
            return this;
        }

        public Builder addLogProxy(ILogProxy logProxy){
            checkPrinter();
            printer.addLogProxy(logProxy);
            return this;
        }


        private void checkPrinter(){
            if (printer == null) {
                printer = new Printer();
            }
        }

        private void checkLogProxyList(){
            if (printer.getLogProxyList().size() == 0) {
                printer.addLogProxy(new AndroidLogProxy());
            }
        }

        @NonNull
        public Logger build() {
            checkPrinter();
            checkLogProxyList();
            return new Logger(this);
        }
    }
}
